﻿using System;
using System.ComponentModel;

namespace Microsoft.WowAddonStudio.FrameXml.Components.Descriptors
{
    public class FrameXmlTypeDescriptionProvider<T> : TypeDescriptionProvider where T : class
    {
        private readonly T instance;
        private readonly string propertyName;

        /// <summary>
        /// Initializes a new instance of the <see cref="FrameXmlTypeDescriptionProvider{T}"/> class.
        /// </summary>
        /// <param name="parent">The parent.</param>
        /// <param name="instance">The inheritable object.</param>
        /// <param name="propertyName">Name of the property.</param>
        public FrameXmlTypeDescriptionProvider(TypeDescriptionProvider parent, T instance, string propertyName)
            : base(parent)
        {
            if (instance == null)
                throw new ArgumentNullException("instance");

            this.instance = instance;
            this.propertyName = propertyName;
        }

        /// <summary>
        /// Initializes a new instance of the <see cref="FrameXmlTypeDescriptionProvider{T}"/> class.
        /// </summary>
        /// <param name="parent">The parent.</param>
        /// <param name="instance">The inheritable object.</param>
        public FrameXmlTypeDescriptionProvider(TypeDescriptionProvider parent, T instance)
            : this(parent, instance, null)
        {
        }

        /// <summary>
        /// Gets a custom type descriptor for the given type and object.
        /// </summary>
        /// <param name="objectType">The type of object for which to retrieve the type descriptor.</param>
        /// <param name="instance">An instance of the type. Can be null if no instance was passed to the <see cref="T:System.ComponentModel.TypeDescriptor"/>.</param>
        /// <returns>
        /// An <see cref="T:System.ComponentModel.ICustomTypeDescriptor"/> that can provide metadata for the type.
        /// </returns>
        public override ICustomTypeDescriptor GetTypeDescriptor(Type objectType, object instance)
        {
            if (instance != null)
                return new FrameXmlCustomTypeDescriptor<T>(GetTypeDescriptor(objectType), this.instance, propertyName);

            return base.GetTypeDescriptor(objectType, instance);
        }
    }
}
